import axios from 'axios'
import router from '@/router'
import { getBaseUrl } from '@/utils/tools'
import { blobToJson } from '@/utils/file'
import { useSystemStore } from '@/stores/system'
import { TOKEN_KEY } from '@/constants'

const baseURL = getBaseUrl()

export const http = axios.create({
    baseURL
})

http.interceptors.request.use(config => {
    withToken(config)
    return config
}, function (error) {
    return Promise.reject(error)
})

http.interceptors.response.use(async response => {
    const isJson = response.headers[`content-type`] && response.headers[`content-type`].indexOf('application/json') !== -1
    
    // blob
    if (response.config.responseType === `blob`) {
        const isJsonBlob = response.data.type.indexOf('application/json') !== -1
        if (isJsonBlob) {
            response.data = await blobToJson(response.data)
        } else {
            return response
        }
    }

    switch (response.data.flag) {
        case 200: // 成功
            break
        case 204: // 操作已经执行成功, 但是没有返回数据
        case 205: // 空指针, 运行时异常
            return Promise.reject(response)
        case 401: // 未授权
            if (router.currentRoute.value.path !== '/login') {
                const systemStore = useSystemStore()
                systemStore.logout(false)
            }
            return Promise.reject(response)
        case 403: // 部分接口受限
        case 404: // 资源, 服务未找到
        case 405: // 不允许的http方法
        case 500: // 系统内部错误
        case 501: // 接口未实现
        case 503: // 网关异常: 服务未找到
            return Promise.reject(response)
        default:
            break
    }
    
    return response.data
}, error => {
    if (axios.isCancel(error)) {
        return Promise.reject(error)
    }
    switch (error.response.status) {
        case 400:
        case 405:
            const badRequest = { msg: error.response.statusText, ...error.response.data }
            error.response.data = badRequest
            break
        case 500:
            const serverErrorData = { msg: error.response.statusText }
            error.response.data = serverErrorData
            break
        default:
            break
    }
    return Promise.reject(error.response)
})

export default http

function withToken (config) {
    const token = localStorage.getItem(TOKEN_KEY)
    if (token) {
        config.headers.token = token
    }
}

/**
 * get方法，对应get请求
 * @param {String} url [请求的url地址]
 * @param {Object} params [请求时携带的参数]
 */
export function get (url, params) {
    return http.get(url, { params }).then(res => res.data)
}

/**
 * post方法，对应post请求
 * @param {String} url [请求的url地址]
 * @param {Object} params [请求时携带的参数]
*/
export function post (url, params) {
    return http.post(url, params).then(res => res.data)
}

/**
 * httpDelete, 对应delete方法
 * @param {String} url [请求的url地址]
 * @param {Object} params [请求时携带的参数]
*/
export function httpDelete (url, params) {
    return http.delete(`${url}/${params}`).then(res => res.data)
}

/**
 * httpDetail, 直接拼接kid
 * @param {String} url [请求的url地址]
 * @param {Object} params [请求时携带的参数]
*/
export function httpDetail (url, params) {
    return http.get(`${url}/${params}`).then(res => res.data)
}

/**
 * put, 更新方法
 * @param {String} url [请求的url地址]
 * @param {Object} params [请求时携带的参数]
*/
export function put (url, params) {
    return http.put(url, params).then(res => res.data)
}